home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
Libris Britannia 4
/
science library(b).zip
/
science library(b)
/
PROGRAMM
/
PASCAL
/
0920.ZIP
/
READEN.ARC
/
READENV.PAS
< prev
Wrap
Pascal/Delphi Source File
|
1987-12-25
|
7KB
|
201 lines
Program Read_Environment_Variables;
{ Program function:
1. read variables in the DOS environment and print a list
2. locate one variable: 'PATH'.
3. store the contents of each directory (delimited by a ';')
in an array
4. print the contents of the array
Program limitations:
1. Requires DOS 3.0 or later for procedure Get_PSP.
2. Environment space: 32K bytes max
Path variable: 1K bytes max.
3. Does not read lowercase chars if in the path (byte values 97..122).
}
{ Downloaded 12/19/87 from cis:bproga:dl4 TPascal V3.0 code
6/21/87 John T. McCann Compuserve ID [72617,710]
Programmer for Integrity Software, we make network utilities
for Novell Netware Networks
12/24/87 Michael Shunfenthal Compuserve ID [76320,122]
Added from original 6/21/87:
1. upgrade to V4.0
2. prints additional error message
3. rearranged and added procedures to modularize funtions
Remove bugs:
1. able to display more than one screen
2. find PATH when it is the first variable in the environment
3. ignore PATH even if part of the name of another var, like BPATH
}
Uses
Crt, Dos;
Const
TotalPaths = 20; { max number of directories in the path }
var
Segment, { the two parts of an address }
offset,
offsetvarstart, { offset wher the 'P' in PATH... begins }
pc, { when searching: character-in-path counter }
pcl : Integer; { when searching: number-of-directories counter }
Paths : Array[1..TotalPaths] of Array[1..255] of Byte;
Procedure Get_PSP; { get the program segment prefix }
var
Regs : Registers;
PSP : Integer;
Begin
Regs.AX := $6200; { Get PSP address }
MsDos(Regs); { Call DOS, int 0x21 }
PSP := Regs.BX; { BX has our PSP }
Segment := MemW[PSP:$2C]; { the offset of $2C indicates the starting
place in memory of our current environment
string }
End; { Get_PSP }
Procedure Read_Env;
{ read the environment area, searching for variables delimited by a null }
procedure locatevariable;
{ search for the specified variable: 'PATH'}
begin
{ parse argument, process search sequentially }
if (Mem[Segment:offset] = ord('P')) and
(Mem[Segment:offset+1] = ord('A')) and
(Mem[Segment:offset+2] = ord('T')) and
(Mem[Segment:offset+3] = ord('H'))
then
offsetvarstart:=offset; { mark where variable begins in memory }
end; { locatevariable }
Begin { Read_Env }
offset := -1; { set initial offsets }
offsetvarstart := -1;
TextColor(7);
ClrScr;
Writeln('The DOS environment variables');
TextColor(3);
While (offset < 32000) do { stop after reading the first 1000
characters of the DOS environment }
begin
offset := offset + 1; { increment the offset by one }
{ call locatevariable to see if it is the first variable
in the environment }
if offset = 0 then locatevariable;
if Mem[Segment:offset] = 0 then
begin
if Mem[Segment:offset+1] = 0 then
begin
{ two nulls in a row indicate the end of the environment. }
TextColor(9);
writeln(#10#10#13'The DOS environment is ',offset,' bytes long.',
' PATH located at offset: ', offsetvarstart);
exit
end
else { a single null indicates the end of one variable,
so the call to locatevariable will not find one
as part of another }
begin
offset := offset + 1;
locatevariable;
offset := offset - 1;
writeln;
end
end
else { not a null }
begin
write(chr(Mem[Segment:offset])); { print any value but 0 (null) }
end
End; { end while loop }
End; { Read_Env }
Procedure StorePath;
{ search for each directory delimited by a ';' and store it in an array }
var
Newoff : integer;
Begin { initialize the array to nulls }
for pc:=1 to TotalPaths do FillChar(paths,255,0);
pc := 0;
pcl := 1;
{
Found PATH= thus first 5 bytes are PATH= so skip it, then parse by ;
}
Newoff := offsetvarstart+5; { see skip message above }
While Newoff< offsetvarstart+1000 do { presuming PATH is smaller than 1000 chars }
begin
if Mem[Segment:NewOff]=0 then
Newoff:=offsetvarstart+1024 { null found, so PATH Search is Complete }
else
if Mem[Segment:Newoff] in [33..41,44..59,61,64..90,92] then
{ are they allowable directory chars? }
if Mem[Segment:Newoff] in [59] then { [59] is the ';', the PATH delim }
begin { end of one subdirectory }
if pcl = TotalPaths then
begin
writeln('Too many Paths encountered... exiting');
Halt(1); { return to DOS with ErrorLevel set to 1 }
end;
pc := 0; pcl := pcl+1; { reset char, increment directory counts }
end
else
begin { save the path character in an array }
pc := pc+1;
paths[pcl][pc]:=Mem[Segment:Newoff];
end;
Newoff := Newoff + 1;
end;
end; { StorePath }
Procedure ListPath;
{ display each directory in the path }
var
a, { when displaying: character-in-path counter }
b : integer; { when displaying: number-of-directories counter }
begin
TextColor(12);
writeln;
writeln('Number of directories: ', pcl, '. Your current path is:');
Textcolor(5); { print each directory in the path on a new line }
If pcl > 1
Then
For a:=1 to pcl do { a counts directories in the array }
begin
b:=1; { b counts characters (first index) in the array }
While b < 255 do
if paths[a][b] in [32..95] then
begin
{ it is a printable char }
write(chr(paths[a][b]));
b:=b+1;
end
else { it is NOT printable... }
b:=256; { something greater than 255 to get us out of while }
writeln; { a new line }
end { of for loop }
else
Writeln('No PATHs in current environment');
end; { ListPath }
Begin { of main program }
Get_PSP;
Read_Env;
if offsetvarstart > -1 then
begin { if offsetvarstart has not been changed from its initial }
StorePath; { setting to -1, then the variable has not been found }
ListPath;
end
else
writeln ('No path found');
End. { of main program }